package com.xposed.xinhao;

import android.app.Activity;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.os.Bundle;

import com.xposed.xinhao.utils.JsonUtils;
import com.xposed.xinhao.utils.LogUtils;

import org.json.JSONException;
import org.json.JSONObject;

import java.io.IOException;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.Locale;

import de.robv.android.xposed.XC_MethodHook;
import de.robv.android.xposed.XSharedPreferences;
import de.robv.android.xposed.XposedHelpers;
import de.robv.android.xposed.callbacks.XC_LoadPackage;
import okhttp3.FormBody;
import okhttp3.OkHttpClient;
import okhttp3.Request;
import okhttp3.Response;
import okhttp3.ResponseBody;

public class YiqianbaoHook {

    private static final String TAG = "MainXposed";
    private static final String RECEIVER_ACTION_YQB_GET_QR_CODE = "com.xposed.hook.yiqianbao.ACTION_YQB_GET_QR_CODE";
    private static final String RECEIVER_ACTION_YQB_SEND_QR_CODE = "com.xposed.hook.yiqianbao.ACTION_YQB_SEND_QR_CODE";

    //保存上下文
    private Context mContext;

    private XC_LoadPackage.LoadPackageParam lpparam;

    public YiqianbaoHook(XC_LoadPackage.LoadPackageParam lpparam) {
        this.lpparam = lpparam;
    }


    public void hookMethod() {

        XposedHelpers.findAndHookMethod(Activity.class, "onCreate", Bundle.class, new XC_MethodHook() {
            @Override
            protected void afterHookedMethod(MethodHookParam param) throws Throwable {
                super.afterHookedMethod(param);
                mContext = (Context) param.thisObject;

                LogUtils.e("Activity onCreate：" + mContext.getClass().getName());
                if (mContext.getClass().getName().equals("com.yeepay.mpos.money.activity.MainActivity")) {
//                    YQBBroadcastReceiver receiver = new YQBBroadcastReceiver();
//                    IntentFilter intentFilter = new IntentFilter();
//                    intentFilter.addAction(RECEIVER_ACTION_YQB_GET_QR_CODE);
//                    (mContext).registerReceiver(receiver, intentFilter);
                    LogUtils.e("com.yeepay.mpos.money.activity.MainActivity 注册广播");

                    try {

                        hookMposInfo();
//                        XposedHelpers.findAndHookMethod("java.util.HashMap", mContext.getClassLoader(), "put", Object.class,Object.class, new XC_MethodHook() {
//                            @Override
//                            protected void beforeHookedMethod(MethodHookParam param) throws Throwable {
//                                super.beforeHookedMethod(param);
//                                LogUtils.e(param.args[0] + "------append-------------" + param.args[1]);
//                            }
//                        });


//                        Class<?> cls = XposedHelpers.findClassIfExists("java.util.ArrayList", lpparam.classLoader);
//                        LogUtils.e("dfd---" + cls.getName());
//                        XposedHelpers.findAndHookMethod(cls, "add", Object.class, new XC_MethodHook() {
//                            @Override
//                            protected void beforeHookedMethod(MethodHookParam param) throws Throwable {
//                                super.beforeHookedMethod(param);
//                                LogUtils.e("-------b--------" + param.args[0]);
//                            }
//                        });
                    } catch (Exception e) {
                        LogUtils.e(e.getMessage());
                    }

//                    XposedHelpers.findAndHookMethod("com.yeepay.mpos.money.activity.MainActivity$2", mContext.getClassLoader(), "onSuccess", String.class, new XC_MethodHook() {
//                        @Override
//                        protected void beforeHookedMethod(MethodHookParam param) throws Throwable {
//                            super.beforeHookedMethod(param);
//                            LogUtils.e("-------onSuccess--------" + param.args[0]);
//                        }
//                    });
                }

                if (mContext.getClass().getName().equals("com.yeepay.mpos.money.activity.LoginActivity")) {

                    XposedHelpers.findAndHookMethod("com.yeepay.mpos.money.activity.LoginActivity$4", mContext.getClassLoader(), "onPostExecute", String.class, new XC_MethodHook() {
                        @Override
                        protected void afterHookedMethod(MethodHookParam param) throws Throwable {
                            super.afterHookedMethod(param);
                            LogUtils.e("-------onPostExecute--------" + param.args[0]);
                        }
                    });
                }

            }
        });

//        XposedHelpers.findAndHookConstructor("org.json.JSONObject", lpparam.classLoader, String.class, new XC_MethodHook() {
//            @Override
//            protected void afterHookedMethod(MethodHookParam param) throws Throwable {
//                super.afterHookedMethod(param);
//                LogUtils.e("---------------" + param.args[0]);
//            }
//        });
    }

    /**
     * hook获取clientId字段信息，该字段信息必须每次重新登录即可获取相关数据
     * */


    private XC_MethodHook.Unhook unhookURLEncoder;
    private void hookClientId(){
        if (unhookURLEncoder == null) {
            unhookURLEncoder = XposedHelpers.findAndHookMethod("java.net.URLEncoder", mContext.getClassLoader(), "encode", String.class, String.class, new XC_MethodHook() {
                @Override
                protected void afterHookedMethod(MethodHookParam param) throws Throwable {
                    super.afterHookedMethod(param);
                    String str = (String) param.args[0];
                    if (str.length() == 16){
                        LogUtils.e("--------------" + str);
                    }
                }
            });
        }
    }

    /**
     * hook获取posCati字段信息，登录成功后进入“刷卡收款”或是“云闪付收款”界面即可获取相关数据
     * */
    private void hookMposInfo() {

        Class<?> cls = XposedHelpers.findClassIfExists("com.yeepay.mpos.money.model.BindMposInfoModel", mContext.getClassLoader());
        XposedHelpers.findAndHookConstructor(cls, new XC_MethodHook() {
            @Override
            protected void afterHookedMethod(final MethodHookParam param) throws Throwable {
                super.afterHookedMethod(param);
                new Thread(new Runnable() {
                    @Override
                    public void run() {
                        try {
                            Thread.sleep(500);
                        } catch (InterruptedException e) {
                            e.printStackTrace();
                        }
                        //获取数据详情 参数：{"createTime":"1571042253964","defaultPos":"TRUE","merchantNo":"10081905610","posCati":"11731098","posName":"DQ00180000125","serialNumber":"0000570380000125"}
                        LogUtils.e("MposInfo:" + JsonUtils.objectToString(param.thisObject));
                        //获取posCati字段数据 参数：posCati:11731098
                        Object posCati = XposedHelpers.getObjectField(param.thisObject, "posCati");
                        LogUtils.e("posCati:" + posCati);
                    }
                }).start();
            }
        });
    }

    /**
     * http请求-收款码
     */
    private void doPostGetQrCode(String serialNumber, String merchantNo, String amount, String token) {
        LogUtils.e("----发送收款码请求----");
        OkHttpClient client = new OkHttpClient();
        SimpleDateFormat sdf = new SimpleDateFormat("yyMMddHHmmssSSS", Locale.getDefault());
        FormBody.Builder builder = new FormBody.Builder()
                .add("serialNumber", serialNumber)
                .add("version", "00")
                .add("posCati", "11731098")
                .add("app", "MPOS")
                .add("merchantNo", merchantNo)
                .add("tradeTime", sdf.format(new Date()))
                .add("payWay", "UNIONPAY")
                .add("amount", amount)
                .add("currcyCode", "156")
                .add("payScenceType", "ACTIVE")
                .add("lg", "119.339303")
                .add("lt", "26.053960")
                .add("province", "福建省")
                .add("city", "福州市")
                .add("address", "福建省福州市台江区光明南路8号靠近升龙汇金中心");
        Request request = new Request.Builder()
                .url("https://openapi.yeepay.com/yop-center/rest/v1.0/ewallet-mpos/yop-postrx/mpos-paylink")
                .post(builder.build())
                .addHeader("Content-Type", "application/x-www-form-urlencoded")
                .addHeader("Connection", "Keep-Alive")
                .addHeader("Authorization", "Bearer " + token)
                .addHeader("Accept", "*/*")
                .addHeader("Cache-Control", "no-cache")
                .addHeader("Host", "openapi.yeepay.com")
                .build();
        try {
            Response response = client.newCall(request).execute();
            if (response.code() != 200)
                return;
            ResponseBody body = response.body();
            if (body == null)
                return;
            String string = body.string().replace("\n", "").replace(" ", "");
            LogUtils.e(string);
            JSONObject jsonObject = new JSONObject(string);
            if (!jsonObject.optString("state").equals("SUCCESS"))
                return;
            JSONObject result = jsonObject.optJSONObject("result");
            if (!result.optString("code").equals("00"))
                return;
            String payUrl = result.optString("payUrl");
            String tradeSerialNo = result.optString("tradeSerialNo");
            LogUtils.e(payUrl + "," + tradeSerialNo);

            Intent intent = new Intent();
            intent.setAction(RECEIVER_ACTION_YQB_SEND_QR_CODE);
            intent.putExtra("payUrl", payUrl);
            intent.putExtra("tradeSerialNo", tradeSerialNo);
            mContext.sendBroadcast(intent);
        } catch (IOException | JSONException e) {
            e.printStackTrace();
        }
    }

    /**
     * 获取token值
     */
    private String getAccessToken() {
        XSharedPreferences xsp = new XSharedPreferences("com.yeepay.mpos.money", "config");
        return xsp.getString("accessToken", "null");
    }

    /**
     * 获取序列号
     */
    private String getSerialNumber() {
        XSharedPreferences xsp = new XSharedPreferences("com.yeepay.mpos.money", "config");
        return xsp.getString("defaultMposSN", "null");
    }

    /**
     * 获取商户号
     */
    private String getMerchantNo() {
        XSharedPreferences xsp = new XSharedPreferences("com.yeepay.mpos.money", "config");
        return xsp.getString("merchantNo", "null");
    }

    /**
     * 广播监听
     */
    private class YQBBroadcastReceiver extends BroadcastReceiver {

        @Override
        public void onReceive(Context context, Intent intent) {
            if (intent.getAction() == null)
                return;
            if (intent.getAction().equals(RECEIVER_ACTION_YQB_GET_QR_CODE)) {
                LogUtils.e("接受到广播-获取收款码");
                String amount = intent.getStringExtra("amount");
                new Thread(new QrCodeRunnable(amount)).start();
            }
        }

        class QrCodeRunnable implements Runnable {

            String amount;

            QrCodeRunnable(String amount) {
                this.amount = amount;
            }

            @Override
            public void run() {
                doPostGetQrCode(getSerialNumber(), getMerchantNo(), amount, getAccessToken());
            }
        }
    }

}
